#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <linux/types.h>
#include<stdbool.h>
#include <string.h>
#include <unistd.h>
#include <sys/syscall.h>
#include <pthread.h>

#include "binder.h"

#define LOG_TAG "BinderServer"
#include <log/log.h>

// Hello Service 命令定义
#define HELLO_SVR_CMD_SAYHELLO     1
#define HELLO_SVR_CMD_SAYHELLO_TO  2

// Food Service 命令定义  
#define FOOD_SVR_CMD_ORDER_FOOD    1

// 服务注册表结构
typedef struct {
    void *service_ptr;           // 服务对象指针
    binder_handler handler;      // 服务处理函数
    char service_name[64];       // 服务名称
} service_entry_t;

// 全局服务注册表
#define MAX_SERVICES 10
static service_entry_t g_service_registry[MAX_SERVICES];
static int g_service_count = 0;
static pthread_mutex_t g_registry_mutex = PTHREAD_MUTEX_INITIALIZER;

#define MAX_THREADS                6

/**
 * 注册服务到服务注册表
 * @param service_ptr 服务对象指针
 * @param handler 服务处理函数
 * @param service_name 服务名称
 * @return 0 成功，-1 失败
 */
int register_service(void *service_ptr, binder_handler handler, const char *service_name) {
    pthread_mutex_lock(&g_registry_mutex);
    
    if (g_service_count >= MAX_SERVICES) {
        printf("[SERVICE_REGISTRY] Error: Maximum services reached\n");
        pthread_mutex_unlock(&g_registry_mutex);
        return -1;
    }
    
    g_service_registry[g_service_count].service_ptr = service_ptr;
    g_service_registry[g_service_count].handler = handler;
    strncpy(g_service_registry[g_service_count].service_name, service_name, 63);
    g_service_registry[g_service_count].service_name[63] = '\0';
    
    printf("[SERVICE_REGISTRY] Registered service '%s' with ptr=%p, handler=%p\n", 
           service_name, service_ptr, handler);
    
    g_service_count++;
    pthread_mutex_unlock(&g_registry_mutex);
    return 0;
}

/**
 * 根据服务对象指针查找对应的处理函数
 * @param service_ptr 服务对象指针
 * @return 对应的处理函数，如果未找到返回 NULL
 */
binder_handler find_service_handler(void *service_ptr) {
    pthread_mutex_lock(&g_registry_mutex);
    
    for (int i = 0; i < g_service_count; i++) {
        if (g_service_registry[i].service_ptr == service_ptr) {
            binder_handler handler = g_service_registry[i].handler;
            printf("[SERVICE_REGISTRY] Found handler %p for service ptr %p (%s)\n", 
                   handler, service_ptr, g_service_registry[i].service_name);
            pthread_mutex_unlock(&g_registry_mutex);
            return handler;
        }
    }
    
    printf("[SERVICE_REGISTRY] Warning: No handler found for service ptr %p\n", service_ptr);
    pthread_mutex_unlock(&g_registry_mutex);
    return NULL;
}


/**
 * 服务端的 hello 服务实现
 * @param name 客户端传递的名称
 * @return 返回格式化的问候语
 */
int sayhello(void)
{
    ATRACE_BEGIN_FUNC("sayhello");
    static int cnt = 0;
    pid_t pid = getpid();
    pid_t tid = syscall(SYS_gettid);
    
    printf("[HELLO_SERVICE][PID:%d,TID:%d] Hello, I am binder service! cnt = %d\n", pid, tid, ++cnt);
    ATRACE_END_FUNC();
    return 0;
}

/**
 * 服务端的 hello_to 服务实现
 * @param name 客户端传递的名称
 * @return 返回格式化的问候语
 */
int sayhello_to(char *name)
{
    ATRACE_BEGIN_FUNC("sayhello_to");
    static int cnt = 0;
    pid_t pid = getpid();
    pid_t tid = syscall(SYS_gettid);
    
    printf("[HELLO_TO_SERVICE][PID:%d,TID:%d] Hello %s, I am binder service! cnt = %d\n", pid, tid, name, ++cnt);
    ATRACE_END_FUNC();
    return 0;
}

/**
 * 点外卖服务函数
 * @param food_name 外卖名称
 * @return 订单号
 */
int order_food(char *food_name)
{
    ATRACE_BEGIN_FUNC("order_food");
    static int order_id = 1000;
    pid_t pid = getpid();
    pid_t tid = syscall(SYS_gettid);
    
    printf("[ORDER_FOOD_SERVICE][PID:%d,TID:%d] 正在为您点外卖: %s\n", pid, tid, food_name);
    usleep(200 * 1000); // 模拟点外卖处理时间 200ms
    printf("[ORDER_FOOD_SERVICE][PID:%d,TID:%d] 外卖 %s 订购成功！订单号: %d\n", pid, tid, food_name, ++order_id);
    ATRACE_END_FUNC();
    return order_id;
}

/**
 * hello 服务的处理函数
 * 只处理 hello 相关的命令
 */
int hello_service_handler(struct binder_state *bs,
                         struct binder_transaction_data_secctx *txn_secctx,
                         struct binder_io *msg,
                         struct binder_io *reply)
{
    ATRACE_BEGIN_FUNC("hello_service_handler");
    struct binder_transaction_data *txn = &txn_secctx->transaction_data;
    
    // 获取当前线程信息用于日志
    pid_t pid = getpid();
    pid_t tid = syscall(SYS_gettid);
    
    printf("[HELLO_SERVICE][PID:%d,TID:%d] Received transaction, code=%u\n", pid, tid, txn->code);

    // 跳过严格模式头部 - 读取 uint32
    uint32_t strict_mode_header = bio_get_uint32(msg);
    
    // 读取服务接口名称
    uint16_t *service_name = bio_get_string16(msg, 0);
    if (service_name == NULL) {
        printf("[HELLO_SERVICE][PID:%d,TID:%d] ERROR: Failed to get service name\n", pid, tid);
        ATRACE_END_FUNC();
        return -1;
    }

    usleep(1 * 1000 * 1000); // 模拟处理延迟
    switch(txn->code) {
    case HELLO_SVR_CMD_SAYHELLO: {
        printf("[HELLO_SERVICE][PID:%d,TID:%d] Processing HELLO_SVR_CMD_SAYHELLO\n", pid, tid);
        sayhello();
        bio_put_uint32(reply, 0); /* no exception */
        ATRACE_END_FUNC();
        return 0;
    }
    case HELLO_SVR_CMD_SAYHELLO_TO: {
        printf("[HELLO_SERVICE][PID:%d,TID:%d] Processing HELLO_SVR_CMD_SAYHELLO_TO\n", pid, tid);
        /* 获取字符串参数 */
        uint16_t *name_utf16 = bio_get_string16(msg, 0);
        if (name_utf16 == NULL) {
            printf("[HELLO_SERVICE][PID:%d,TID:%d] ERROR: Failed to get name parameter\n", pid, tid);
            bio_put_uint32(reply, -1); /* exception */
            ATRACE_END_FUNC();
            return -1;
        }
        
        /* 转换为 ASCII 字符串 */
        char name[256];
        int i;
        for (i = 0; name_utf16[i] && i < 255; i++) {
            name[i] = (char)name_utf16[i];
        }
        name[i] = '\0';
        
        sayhello_to(name);
        bio_put_uint32(reply, 0); /* no exception */
        ATRACE_END_FUNC();
        return 0;
    }
    default:
        printf("[HELLO_SERVICE][PID:%d,TID:%d] ERROR: Unknown command %u\n", pid, tid, txn->code);
        ATRACE_END_FUNC();
        return -1;
    }
}

/**
 * food 服务的处理函数
 * 只处理外卖相关的命令
 */
int food_service_handler(struct binder_state *bs,
                        struct binder_transaction_data_secctx *txn_secctx,
                        struct binder_io *msg,
                        struct binder_io *reply)
{
    ATRACE_BEGIN_FUNC("food_service_handler");
    struct binder_transaction_data *txn = &txn_secctx->transaction_data;
    
    // 获取当前线程信息用于日志
    pid_t pid = getpid();
    pid_t tid = syscall(SYS_gettid);
    
    printf("[FOOD_SERVICE][PID:%d,TID:%d] Received transaction, code=%u\n", pid, tid, txn->code);

    // 跳过严格模式头部 - 读取 uint32
    uint32_t strict_mode_header = bio_get_uint32(msg);
    
    // 读取服务接口名称
    uint16_t *service_name = bio_get_string16(msg, 0);
    if (service_name == NULL) {
        printf("[FOOD_SERVICE][PID:%d,TID:%d] ERROR: Failed to get service name\n", pid, tid);
        ATRACE_END_FUNC();
        return -1;
    }

    usleep(500 * 1000); // 模拟处理延迟 500ms
    switch(txn->code) {
    case FOOD_SVR_CMD_ORDER_FOOD: {
        printf("[FOOD_SERVICE][PID:%d,TID:%d] Processing FOOD_SVR_CMD_ORDER_FOOD\n", pid, tid);
        /* 获取外卖名称参数 */
        uint16_t *food_name_utf16 = bio_get_string16(msg, 0);
        if (food_name_utf16 == NULL) {
            printf("[FOOD_SERVICE][PID:%d,TID:%d] ERROR: Failed to get food name parameter\n", pid, tid);
            bio_put_uint32(reply, -1); /* exception */
            ATRACE_END_FUNC();
            return -1;
        }
        
        /* 转换为 ASCII 字符串 */
        char food_name[256];
        int i;
        for (i = 0; food_name_utf16[i] && i < 255; i++) {
            food_name[i] = (char)food_name_utf16[i];
        }
        food_name[i] = '\0';
        
        int order_id = order_food(food_name);
        bio_put_uint32(reply, order_id); /* 返回订单号 */
        ATRACE_END_FUNC();
        return 0;
    }
    default:
        printf("[FOOD_SERVICE][PID:%d,TID:%d] ERROR: Unknown command %u\n", pid, tid, txn->code);
        ATRACE_END_FUNC();
        return -1;
    }
}

/**
 * 统一的服务分发器
 * 根据 target.ptr 查找对应的服务处理函数并调用
 */
int service_dispatcher(struct binder_state *bs,
                      struct binder_transaction_data_secctx *txn_secctx,
                      struct binder_io *msg,
                      struct binder_io *reply)
{
    ATRACE_BEGIN_FUNC("service_dispatcher");
    struct binder_transaction_data *txn = &txn_secctx->transaction_data;
    
    // 获取当前线程信息用于日志
    pid_t pid = getpid();
    pid_t tid = syscall(SYS_gettid);
    
    printf("[SERVICE_DISPATCHER][PID:%d,TID:%d] Received transaction for target=%p, code=%u\n", 
           pid, tid, (void*)txn->target.ptr, txn->code);
    
    // 根据 target.ptr 查找对应的服务处理函数
    binder_handler handler = find_service_handler((void*)txn->target.ptr);
    if (handler == NULL) {
        printf("[SERVICE_DISPATCHER][PID:%d,TID:%d] ERROR: No handler found for target=%p\n", 
               pid, tid, (void*)txn->target.ptr);
        ATRACE_END_FUNC();
        return -1;
    }
    
    printf("[SERVICE_DISPATCHER][PID:%d,TID:%d] Dispatching to handler %p for target=%p\n", 
           pid, tid, handler, (void*)txn->target.ptr);
    
    // 调用对应的服务处理函数
    int result = handler(bs, txn_secctx, msg, reply);
    
    printf("[SERVICE_DISPATCHER][PID:%d,TID:%d] Handler returned %d\n", pid, tid, result);
    ATRACE_END_FUNC();
    return result;
}

// 工作线程参数结构体
struct worker_args {
    struct binder_state *bs;
    int (*service_handler)(struct binder_state *bs,
                          struct binder_transaction_data_secctx *txn_secctx,
                          struct binder_io *msg,
                          struct binder_io *reply);
    const char *service_name;
};

/**
 * binder 工作线程函数
 * 每个工作线程都会执行这个函数，进入 binder_loop 等待处理请求
 */
void *binder_worker(void *arg)
{
    ATRACE_BEGIN_FUNC("binder_worker");
    struct worker_args *args = (struct worker_args *)arg;
    
    // 获取当前线程信息
    pid_t pid = getpid();
    pid_t tid = syscall(SYS_gettid);
    
    printf("[WORKER][PID:%d,TID:%d] Worker thread started for service: %s\n", pid, tid, args->service_name);
    
    // 进入 binder 循环，等待处理请求
    binder_loop(args->bs, args->service_handler);
    
    printf("[WORKER][PID:%d,TID:%d] Worker thread exiting for service: %s\n", pid, tid, args->service_name);
    ATRACE_END_FUNC();
    return NULL;
}

/**
 * 主函数
 * 初始化 binder 服务，创建工作线程池，注册多个服务
 * 主线程不进入 binder_loop，而是管理服务的生命周期
 */
int main(int argc, char **argv)
{
    ATRACE_BEGIN_FUNC("main");
    int ret;
    struct binder_state *bs;
    uint32_t svcmgr = BINDER_SERVICE_MANAGER;
    
    // 获取当前进程信息
    pid_t pid = getpid();
    printf("[MAIN][PID:%d] Binder server starting (like Android system_server)...\n", pid);

    // 打开 binder 设备
    bs = binder_open("/dev/binder", 128*1024);
    if (!bs) {
        fprintf(stderr, "failed to open binder driver\n");
        ATRACE_END_FUNC();
        return -1;
    }

    // 设置最大线程数
    binder_set_maxthreads(bs, MAX_THREADS);
    printf("[MAIN][PID:%d] Set max threads to %d\n", pid, MAX_THREADS);

    // 创建服务对象实例（模拟 Android 中的服务实例）
    static int hello_service_instance = 1;  // 模拟 HelloService 实例
    static int food_service_instance = 2;   // 模拟 FoodService 实例
    
    // 注册服务到本地服务注册表
    printf("[MAIN][PID:%d] Registering services to local registry...\n", pid);
    register_service(&hello_service_instance, hello_service_handler, "hello");
    register_service(&food_service_instance, food_service_handler, "food");

    // 注册 hello 服务到 service manager
    printf("[MAIN][PID:%d] Publishing hello service...\n", pid);
    ret = svcmgr_publish(bs, svcmgr, "hello", &hello_service_instance);
    if (ret) {
        fprintf(stderr, "failed to publish hello service\n");
        ATRACE_END_FUNC();
        return -1;
    }
    printf("[MAIN][PID:%d] Hello service published successfully\n", pid);

    // 注册 food 服务到 service manager
    printf("[MAIN][PID:%d] Publishing food service...\n", pid);
    ret = svcmgr_publish(bs, svcmgr, "food", &food_service_instance);
    if (ret) {
        fprintf(stderr, "failed to publish food service\n");
        ATRACE_END_FUNC();
        return -1;
    }
    printf("[MAIN][PID:%d] Food service published successfully\n", pid);

    // 准备统一分发器的工作线程参数
    struct worker_args dispatcher_args = {bs, service_dispatcher, "unified_dispatcher"};
    
    // 创建统一的工作线程池，所有线程都使用统一分发器
    pthread_t worker_threads[MAX_THREADS];
    
    printf("[MAIN][PID:%d] Creating unified worker threads with service dispatcher...\n", pid);
    for (int i = 0; i < MAX_THREADS; i++) {
        ret = pthread_create(&worker_threads[i], NULL, binder_worker, &dispatcher_args);
        if (ret != 0) {
            fprintf(stderr, "Failed to create worker thread %d: %s\n", i, strerror(ret));
            ATRACE_END_FUNC();
            return -1;
        }
        printf("[MAIN][PID:%d] Created worker thread %d with unified dispatcher\n", pid, i);
    }

    // 主线程不进入 binder_loop，而是管理服务生命周期
    printf("[MAIN][PID:%d] Main thread managing services (not entering binder_loop)...\n", pid);
    printf("[MAIN][PID:%d] Services running: hello, food (like AMS, WMS, PMS in Android)\n", pid);
    
    // 主线程保持运行，监控服务状态
    while (1) {
        sleep(10); // 每10秒检查一次服务状态
        printf("[MAIN][PID:%d] Services health check - hello and food services running\n", pid);
    }

    // 等待所有工作线程结束（实际上不会到达这里）
    for (int i = 0; i < MAX_THREADS; i++) {
        pthread_join(worker_threads[i], NULL);
    }

    printf("[MAIN][PID:%d] Binder server exiting\n", pid);
    ATRACE_END_FUNC();
    return 0;
}